var sockets = []

// 已经加入的房间
var rooms = {}

var socketOptions = {
  // host: '192.168.124.8',
  host: '10.2.2.36',
  port: 8200,
  path: '/enkel',
  room: '/public'
}

var fp = ''

function __loadJS (url) {
  return new Promise((resolve) => {
    var script = document.createElement('script')
    script.type = "text/javascript"
    if (script.readyState) {
      script.onreadystatechange = function () {
        if (script.readyState == "loaded" || script.readyState == "complete") {
          script.onreadystatechange = null
          resolve(true)
        }
      }
    } else {
      script.onload = function () {
        resolve(true)
      }
    }
    script.src = url
    document.body.appendChild(script)
  })
}

function loadJS (scripts) {
  return new Promise(async (resolve) => {
    if (!scripts || (scripts.length == 0)) return resolve(true)
    if (Object.prototype.toString.call(scripts) == '[object String]') {
      await __loadJS(scripts)
      return resolve(true)
    }
    var _scripts = []
    for (var i = 0; i < scripts.length; i++) {
      _scripts.push(__loadJS(scripts[i]))
    }
    await Promise.all(_scripts)
    return resolve(true)
  })
}

function _getEntitySender (id) {
  return {
    id: id || fp,
    name: 'Extension',
    fp: fp
  }
}

var ActionType = {
  connect: '1',
  confirm: '2',
  disconnect: '3',
  joinRoom: '4',
  exitRoom: '5',
  sendUserScript: '101',
  setTabActive: '102',
}

function _getEntityMessage (actionType, data = {}) {
  return {
    action: ActionType[actionType],
    data
  }
}

function _msgHandler (msg = {}, socketId = '') {
  if (socketId == msg.from?.id) return
  var _sender = msg.from
  var _message = msg.data
  var _action = msg.data?.action
  switch (_action) {
    case ActionType.connect:
      console.log(`${_sender.id}[${_sender.name}] 扫码进入了`)
      break
    case ActionType.disconnect:
      console.log(`${_sender.id}[${_sender.name}] 退出了`)
      break
    case ActionType.confirm:
      break
    case ActionType.sendUserScript:
      // console.log('[sendUserScript]: ', msg)
      chrome.tabs.sendMessage(Number(_sender?.tabId), _message?.data, function (response) {
        // console.log('接到response: ', _sender?.tabId, _message?.data)
      })
      break
    case ActionType.setTabActive:
      // console.log('[setTabActive]: ', msg)
      chrome.windows.update(Number(_sender?.winId), {
        focused: true,
      })
      chrome.tabs.update(Number(_sender?.tabId), {
        selected: true,
      })
      break
    case ActionType.joinRoom:
      // joinRoom()
      break
    case ActionType.exitRoom:
      // joinRoom()
      break
  }
}

var socket;

function initSocket () {
  socket = io(`http://${socketOptions.host}:${socketOptions.port}`, {
    path: socketOptions.path || '/enkel',
    transports: ['websocket']
  });//和服务器建立连接

  socket.on('connect', (res) => {
    socket.on('message', (msg) => {
      console.log('>>>>>', msg)
      _msgHandler(msg, socket.id)
    })

    socket.emit('message', {
      from: _getEntitySender(socket.id),
      data: _getEntityMessage('connect')
    })

    sockets = [socket]
  })

  socket.on('disconnect', () => {
    sockets = []
  })

  chrome.tabs.onUpdated.addListener(function (tabId, changeInfo, tab) {

    if (changeInfo.url) {
      // tab url变化，退出房间

      let _room = encodeURIComponent(changeInfo.url.split('?')[0].split('//').pop() + '|' + tabId + '|' + fp)
      console.log('>>>> leave room: ', _room)
      if (rooms[_room]) {
        rooms[_room] = null
        delete rooms[_room]

        socket.emit('message', {
          from: _getEntitySender(socket.id),
          config: {
            room: _room
          },
          data: _getEntityMessage('exitRoom')
        })
      }
    }
  })
}

function joinRoom (roomId, data = { url: '' }) {
  if (!socket) {
    this.initSocket()
  }
  console.log('>>>> join room: ', roomId)
  if (!rooms[roomId]) {
    rooms[roomId] = data

    socket.emit('message', {
      from: _getEntitySender(socket.id),
      config: {
        room: roomId
      },
      data: _getEntityMessage('joinRoom', data)
    })
  }

}

loadJS(['https://lib.baomitu.com/socket.io/4.2.0/socket.io.js', 'https://cdn.jsdelivr.net/npm/@fingerprintjs/fingerprintjs@3/dist/fp.min.js']).then(async () => {
  if (!fp) {
    await FingerprintJS.load({ token: 'your-browser-token' }).then(f => f.get()).then(result => {
      fp = result.visitorId.substring(0, 8)
      // resetSocketOptions({
      //   room: '/' + fp
      // })
    })
  }
  if (sockets.length == 0) {
    initSocket()
  }
})

function resetSocketOptions (params) {
  socketOptions = Object.assign({}, socketOptions, params)
}

